import { useCommonStore } from "@/store/modules/common"
import { useUserStore } from "@/store/modules/user"
import type { EventReceive, Message } from "@/types/chat"
import type { ChatTarget } from "@/types/chatTarget"
import type { GroupNotice } from "@/types/groupNotice"
import io from "socket.io-client"
import { showFailToast, showLoadingToast } from "vant"
import { nextTick, reactive, ref } from "vue"

// 定义消息列表
export const messageList = ref<Message[]>([])

// 定义请求参数
const query = ref<object>({})

// 参数地址：https://socket.io/zh-CN/docs/v4/client-initialization/
// 参数地址：https://socket.io/zh-CN/docs/v2/client-initialization/
// 定义连接参数
const options = reactive({
    transports: [
        // 指定传输方式，如WebSocket
        'websocket',
        // 'polling'
    ],

    // 是否自动连接
    autoConnect: true,

    // 是否自动重新连接
    reconnection: true,

    // 重新连接尝试次数
    reconnectionAttempts: 3,

    // 重新连接延迟时间（毫秒）
    reconnectionDelay: 1000,

    // 指定token,高版本用法
    // auth: {
    //     token: `Bearer ${userStore.profile?.token}`
    // },

    // 自定义查询参数
    query,
    // 其他可选参数...
    // path: '/socket.io',
})

// 设置请求参数
export const setQuery = (params: object) => {
    query.value = params
}

export const socket = ref()

// 加载提示框
export const loadingInstance = ref()

// 初始化socket.io
export const initSocketIO = (socketioSrvUrl: string) => {
    // socket.value = io(import.meta.env.VITE_SOCKET_IO_SERVER, options)
    socket.value = io(socketioSrvUrl, options)

    loadingInstance.value = showLoadingToast({
        message: '拼命加载中',
        // background: 'rgba(0, 0, 0, 0.8)'
    })

    // 监听连接事件
    socket.value.on('connect', function() {
        // showToast('连接成功')
        console.log(' ------------------- 监听连接事件 ------------------- ')
        console.log(socket.value)
        loadingInstance.value.close()
    })

    // 接收服务器默认消息事件
    socket.value.on('receive-defult-message', async function({data}: {data: Message[]}) {
        loadingInstance.value.close()
        messageList.value.push(...data);
        console.log('receive-defult-message =', data);

        // 始终显示新一条消息
        await nextTick()
        window.scrollTo(0, document.body.scrollHeight)
    })

    // 用户存储
    const userStore = useUserStore()

    // 公共存储
    const commonStore = useCommonStore()

    // 接收私聊消息事件
    socket.value.on('receive-private-chat', async function({data}: {data: Message}) {
        console.log(' ------------------- 接收私聊消息事件 ------------------- ')
        console.log('data =', data);

        console.log('currentRouteUrl = ', commonStore.currentRouteUrl);
        
        // 如果当前页面是聊天页面,则发送设置消息为已读消息
        if (commonStore.currentRouteUrl == '/chat') {
            console.log(' +++++++++++++ 设置消息为已读 +++++++++++++ ')
            // 设置消息为已读
            data.is_read = 1
            socket.value.emit('read-message', {id: data.id})

            loadingInstance.value.close()
            messageList.value.push(data);
            console.log('receive-private-chat =', data);
        }

        // 如果当前页不是聊天页面,则打开对话框、将最后一条消息修改为当前消息
        if (commonStore.currentRouteUrl != '/chat') {
            console.log(' +++++++++++++ 打开聊天对象 +++++++++++++ ')
            socket.value.emit('open-chat-target', {
                uid: data.to_uid,
                mode: 1,
                target_info: {
                    name: data.from_user?.username,
                    target_id: data.from_user?.uid,
                    avatar_url: data.from_user?.avatar_url
                }
            })
        }

        // 始终显示新一条消息
        await nextTick()
        window.scrollTo(0, document.body.scrollHeight)
    })

    // 接收群聊消息事件
    socket.value.on('receive-group-chat', async function({data}: {data: Message}) {
        console.log(' ------------------- 接收群聊消息事件 ------------------- ');
        
        console.log('data =', data);

        // 如果当前页面是聊天页面,则发送设置消息为已读消息
        if (commonStore.currentRouteUrl == '/chat') {
            console.log(' +++++++++++++ 设置消息为已读 +++++++++++++ ')
            // 设置消息为已读
            data.is_read = 1
            socket.value.emit('read-message', {id: data.id})

            loadingInstance.value.close()
            // 判断当前消息是否为当前用户发送,如果不是当前用户发送的消息则添加到消息列表
            // 反之则不添加，因为在发送消息之前已经添加过了
            if (data.from_uid != userStore.profile.user.uid) {
                messageList.value.push(data);
            }
            console.log('receive-group-chat =', data);
        }
        
        // 如果当前页面是首页,则将最后一条消息修改为当前消息
        if (commonStore.currentRouteUrl == '/') {
            console.log(' +++++++++++++ 打开聊天对象 +++++++++++++ ')
            socket.value.emit('open-chat-target', {
                uid: userStore.profile.user.uid,
                mode: 2,
                target_info: {
                    target_id: data.to_uid
                }
            })
        }

        // 始终显示新一条消息
        await nextTick()
        window.scrollTo(0, document.body.scrollHeight)
    })

    // 接收加入群消息事件
    socket.value.on('receive-join-group-broadcast', async function({data}: {data: Message}) {
        console.log(' ------------------- 接收加入群消息事件 ------------------- ')
        console.log('data =', data);
        socket.value.emit('join-group', data)
    })

    // 接收移除群消息事件
    socket.value.on('receive-remove-group-broadcast', async function({data}: {data: Message}) {
        console.log(' ------------------- 接收移除群消息事件 ------------------- ')
        console.log('data =', data);
        socket.value.emit('remove-group', data)
    })

    // 接收广播消息事件
    socket.value.on('receive-broadcast', async function({data}: {data: Message}) {
        console.log(' ------------------- 接收广播消息事件 ------------------- ')
        console.log('data =', data);

        loadingInstance.value.close()
        messageList.value.push(data);
        console.log('receive-broadcast =', data);

        // 始终显示新一条消息
        await nextTick()
        window.scrollTo(0, document.body.scrollHeight)
    })

    // 接收打开聊天对象事件
    socket.value.on('receive-open-chat-target', async function({data}: {data: ChatTarget}) {
        console.log(' ------------------- 接收打开聊天对象事件 ------------------- ')
        console.log('data =', data);
        // 公共存储
        const commonStore = useCommonStore()
        const index = commonStore.chatTargetList.findIndex(item => item.id == data.id)
        if (index != -1) { // 编辑
            data.unread_num = commonStore.chatTargetList[index].unread_num + 1
            console.log('data = ', data);
            
            commonStore.editChatTarget(data)
        } else { // 添加
            data.unread_num = 1
            commonStore.addChatTarget(data)
        }
    })

    // 接收群公告事件
    socket.value.on('receive-group-notice', async function({data}: {data: Message}) {
        console.log(' ------------------- 接收群公告事件 ------------------- ')
        console.log('data =', data);
        // 如果当前页面是聊天页面,则发送设置消息为已读消息
        if (commonStore.currentRouteUrl == '/chat') {
            console.log(' +++++++++++++ 设置消息为已读 +++++++++++++ ')
            // 设置消息为已读
            data.is_read = 1
            socket.value.emit('read-message', {id: data.id})

            loadingInstance.value.close()
            messageList.value.push(data)
        }

        // 始终显示新一条消息
        await nextTick()
        window.scrollTo(0, document.body.scrollHeight)
    })

    // 接收好友申请通知事件
    socket.value.on('receive-friend-apply', async function({data}: {data: Message}) {
        console.log(' ------------------- 接收好友申请通知事件 ------------------- ')
        console.log('data =', data);

        loadingInstance.value.close()
        const commonStore = useCommonStore()
        const total = commonStore.friendApplyTotal + 1
        commonStore.setFriendApplyTotal(total)
    })

    // 监听服务器心跳事件
    socket.value.on('pong', (latency: any) => {
        console.log('pong =', latency);
    });

    // 监听失败事件
    socket.value.on('fail', function(result: EventReceive) {
        showFailToast(result.msg)
        console.log('fail =', result)
        console.log('fail message ='+ result.msg)
    });

    // 监听错误事件
    socket.value.on('error', (error: any) => {
        console.log('error =', error);
    });

    // 监听连接错误事件
    socket.value.on('connect_error', (error: any) => {
        showFailToast('连接错误')
        console.log('connect_error =', error);
    });

    // 监听断开连接事件
    socket.value.on('disconnect', function() {
        showFailToast('连接已断开')
        console.log('disconnect');
        console.log(socket.value);
    })
}
